﻿using JTLeigh.Commerce.Spencer.Core.Service;
using JTLeigh.Commerce.Spencer.Features.ProductImages.Common;
using JTLeigh.Commerce.Spencer.Features.ProductImages.Service.Commands.Runtime;
using JTLeigh.Commerce.Spencer.Features.ProductImages.Service.Contracts;
using JTLeigh.Commerce.Spencer.Features.ProductImages.Service.Contracts.Runtime.GetProductImages;
using JTLeigh.Commerce.Spencer.Features.ProductImages.Service.Contracts.Runtime.GetProductImageSnapshot;
using JTLeigh.Commerce.Spencer.Features.ProductImages.Service.Contracts.Runtime.GetProductImageSummaries;
using Microsoft.Practices.EnterpriseLibrary.ExceptionHandling.WCF;
using Microsoft.Practices.Unity;

namespace JTLeigh.Commerce.Spencer.Features.ProductImages.Service
{

	/// <summary>
	/// WCF service implementation for the Product Images service.
	/// </summary>
	/// <remarks>
	/// <para>
	/// Dependencies are injected using <see cref="DependencyInjectionServiceBehaviorAttribute"/> 
	/// which configures the container using the default and <c>ProductImageServices</c> container 
	/// configurations.
	/// </para>
	/// </remarks>
	[ExceptionShielding(ProductImagesExceptionPolicy.Service)]
	[DependencyInjectionServiceBehavior]
	public class ProductImagesRuntimeService : IProductImagesRuntimeService
	{

		#region Properties

		/// <summary>
		/// Gets or sets the dependency injection container to use to resolve dependencies.
		/// </summary>
		/// <remarks>
		/// <para>
		/// Services that have multiple commands with multiple dependencies should depend on 
		/// <see cref="IUnityContainer"/> and use the container to resolve commands on-demand.
		/// </para>
		/// </remarks>
		[Dependency]
		public IUnityContainer Container { get; set; }

		#endregion // Properties

		#region IProductImagesRuntimeService Members

		/// <summary>
		/// Gets all images for a single product, including all views and sizes.
		/// </summary>
		/// <param name="request">The <see cref="GetProductImagesRequest"/> request object.</param>
		/// <returns>The <see cref="GetProductImagesResponse"/> response object.</returns>
		/// <remarks>
		/// <para>
		/// This operation also gets all view and size information relevant to the images returned.
		/// </para>
		/// <para>
		/// Use this operation when you need to display all images for a single product (e.g. on
		/// an &quot;Other Views&quot; page).
		/// </para>
		/// </remarks>
		public GetProductImagesResponse GetProductImages(GetProductImagesRequest request)
		{
			GetProductImagesCommand command;

			command = Container.Resolve<GetProductImagesCommand>();
			return command.GetProductImages(request);
		}

		/// <summary>
		/// Gets a single image for a single product, view, and size combination.
		/// </summary>
		/// <param name="request">The <see cref="GetProductImageSnapshotRequest"/> request object.</param>
		/// <returns>The <see cref="GetProductImageSnapshotResponse"/> response object.</returns>
		/// <remarks>
		/// <para>
		/// This operation also gets a subset of the size information relevant to the image 
		/// returned, and the number of other views and sizes available for the product requested.
		/// </para>
		/// <para>
		/// Use this operation when you need to display a single image for a single product, view,
		/// and size combination (e.g. on a &quot;Product Details&quot; page) and when you need to
		/// know if there are other views and sizes available for the product (e.g. to know when to
		/// display &quot;See Other Views&quot; or &quot;See Other Sizes&quot; hyperlinks).
		/// </para>
		/// </remarks>
		public GetProductImageSnapshotResponse GetProductImageSnapshot(GetProductImageSnapshotRequest request)
		{
			GetProductImageSnapshotCommand command;

			command = Container.Resolve<GetProductImageSnapshotCommand>();
			return command.GetProductImageSnapshot(request);
		}

		/// <summary>
		/// Gets a single image per product for multiple products for a single view and size 
		/// combination.
		/// </summary>
		/// <param name="request">The <see cref="GetProductImageSummariesRequest"/> request object.</param>
		/// <returns>The <see cref="GetProductImageSummariesResponse"/> response object.</returns>
		/// <remarks>
		/// <para>
		/// This operation also gets a subset of the size information relevant to the image 
		/// returned.
		/// </para>
		/// <para>
		/// Use this operation when you need to display a single image per product for multiple 
		/// products for a single view and size combination (e.g. on a &quot;Category&quot; or
		/// &quot;Search Results&quot; page).
		/// </para>
		/// </remarks>
		public GetProductImageSummariesResponse GetProductImageSummaries(GetProductImageSummariesRequest request)
		{
			GetProductImageSummariesCommand command;

			command = Container.Resolve<GetProductImageSummariesCommand>();
			return command.GetProductImageSummaries(request);
		}

		#endregion // IProductImagesRuntimeService Members

	}

}
